#ifndef WS2812_H
#define WS2812_H

#include <esp_err.h>
#include <memory>
#include "led_strip.h"
#include <vector>
#include <functional>
#include <cstdint>

/**
 * ╔══════════════════════════════════════════════════════════════════════════════╗
 * ║                            WS2812 LED灯带控制类                              ║
 * ╚══════════════════════════════════════════════════════════════════════════════╝
 * 
 * 🌈 功能特点：
 * • 支持单个/批量LED颜色控制
 * • 内置8种炫酷动画效果（彩虹、呼吸、追逐等）
 * • 亮度调节（0-100%）
 * • 丰富的颜色工具函数
 * • 动画暂停/恢复控制
 * 
 * 📝 快速上手：
 * ```cpp
 * WS2812 led_strip(GPIO_NUM_8, 30);        // 创建对象：GPIO8，30个LED
 * led_strip.Initialize();                   // 初始化
 * led_strip.SetPixel(0, WS2812::Color::RED); // 第1个LED设为红色
 * led_strip.Rainbow(3000);                  // 彩虹动画，3秒一周期
 * led_strip.SetBrightness(50);             // 设置亮度为50%
 * ```
 */
class WS2812 {
public:
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              颜色结构体                                 ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🎨 RGB颜色结构体
     * 
     * 支持颜色运算：加法、减法、乘法、比较
     * 内置11种常用颜色常量
     * 
     * 💡 使用示例：
     * ```cpp
     * Color red(255, 0, 0);                    // 创建红色
     * Color pink = Color::RED + Color::WHITE;  // 颜色混合
     * Color dim_red = Color::RED * 0.5f;       // 50%亮度的红色
     * ```
     */
    struct Color {
        uint8_t red;    ///< 🔴 红色分量 (0-255)
        uint8_t green;  ///< 🟢 绿色分量 (0-255)
        uint8_t blue;   ///< 🔵 蓝色分量 (0-255)
        
        /// 构造函数
        Color(uint8_t r = 0, uint8_t g = 0, uint8_t b = 0) 
            : red(r), green(g), blue(b) {}
            
        // ✨ 颜色运算符（已实现，可直接使用）
        Color operator+(const Color& other) const;  ///< 颜色相加
        Color operator*(float factor) const;        ///< 亮度调节
        Color operator-(const Color& other) const;  ///< 颜色相减
        bool operator==(const Color& other) const;  ///< 颜色比较
        bool operator!=(const Color& other) const;  ///< 颜色不等
        
        // 🌈 预定义颜色常量（已实现，可直接使用）
        static const Color BLACK;      ///< ⚫ 黑色 (0,0,0)
        static const Color WHITE;      ///< ⚪ 白色 (255,255,255)
        static const Color RED;        ///< 🔴 红色 (255,0,0)
        static const Color GREEN;      ///< 🟢 绿色 (0,255,0)
        static const Color BLUE;       ///< 🔵 蓝色 (0,0,255)
        static const Color YELLOW;     ///< 🟡 黄色 (255,255,0)
        static const Color CYAN;       ///< 🩵 青色 (0,255,255)
        static const Color MAGENTA;    ///< 🟣 洋红色 (255,0,255)
        static const Color ORANGE;     ///< 🟠 橙色 (255,165,0)
        static const Color PURPLE;     ///< 🟣 紫色 (128,0,128)
        static const Color PINK;       ///< 🩷 粉色 (255,192,203)
    };

    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              动画类型                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🎬 动画效果类型
     */
    enum class AnimationType {
        NONE,           ///< 🚫 无动画
        FADE_IN,        ///< 📈 淡入效果
        FADE_OUT,       ///< 📉 淡出效果
        RAINBOW,        ///< 🌈 彩虹循环
        BREATHE,        ///< 💨 呼吸效果
        COLOR_WIPE,     ///< 🖌️ 颜色擦除
        SPARKLE,        ///< ✨ 随机闪烁
        CHASE,          ///< 🏃 追逐效果
        THEATER_CHASE   ///< 🎭 剧院追逐
    };

    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                            构造与析构                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🏗️ 构造函数
     * @param gpio_pin GPIO引脚号（如：GPIO_NUM_8）
     * @param led_count LED数量（如：30）
     * 
     * 💡 示例：WS2812 strip(GPIO_NUM_8, 30);
     */
    WS2812(int gpio_pin, int led_count);
    
    /**
     * 🗑️ 析构函数 - 自动释放资源
     */
    ~WS2812();

    // 🚫 禁用拷贝，确保资源安全
    WS2812(const WS2812&) = delete;
    WS2812& operator=(const WS2812&) = delete;
    
    // ✅ 支持移动语义
    WS2812(WS2812&& other) noexcept;
    WS2812& operator=(WS2812&& other) noexcept;

    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              基本操作                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🚀 初始化LED灯带（必须首先调用）
     * @return ESP_OK=成功，其他=错误码
     * 
     * 💡 示例：strip.Initialize();
     */
    esp_err_t Initialize();
    
    /**
     * 💡 设置单个LED颜色（立即显示）
     * @param index LED索引 (0 到 led_count-1)
     * @param color 颜色对象
     * @return ESP_OK=成功
     * 
     * 💡 示例：strip.SetPixel(0, Color::RED);
     */
    esp_err_t SetPixel(int index, const Color& color);
    
    /**
     * 💡 设置单个LED颜色（RGB值）
     * @param index LED索引
     * @param red 红色 (0-255)
     * @param green 绿色 (0-255)
     * @param blue 蓝色 (0-255)
     * 
     * 💡 示例：strip.SetPixel(0, 255, 0, 0); // 红色
     */
    esp_err_t SetPixel(int index, uint8_t red, uint8_t green, uint8_t blue);
    
    /**
     * 🌟 设置所有LED为相同颜色
     * @param color 颜色对象
     * 
     * 💡 示例：strip.SetAllPixels(Color::BLUE);
     */
    esp_err_t SetAllPixels(const Color& color);
    
    /**
     * 🧹 清除所有LED（全部变黑）
     * 
     * 💡 示例：strip.Clear();
     */
    esp_err_t Clear();
    
    /**
     * 🔄 刷新显示（手动更新LED状态）
     * 
     * 💡 用于批量操作后的统一刷新
     */
    esp_err_t Refresh();
    
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                            批量操作（高性能）                            ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * ⚡ 设置单个LED（不立即显示，需手动Refresh）
     * 
     * 🎯 用途：批量设置多个LED时提高性能
     */
    esp_err_t SetPixelNoRefresh(int index, const Color& color);
    esp_err_t SetPixelNoRefresh(int index, uint8_t red, uint8_t green, uint8_t blue);
    
    /**
     * ⚡ 批量设置多个LED（不立即显示）
     * @param colors 颜色数组
     * @param start_index 起始位置（默认0）
     * 
     * 💡 示例：
     * ```cpp
     * std::vector<Color> colors = {Color::RED, Color::GREEN, Color::BLUE};
     * strip.SetPixelsNoRefresh(colors, 0);
     * strip.Refresh(); // 统一刷新
     * ```
     */
    esp_err_t SetPixelsNoRefresh(const std::vector<Color>& colors, int start_index = 0);

    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              高级功能                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🔆 设置整体亮度
     * @param brightness 亮度 (0-100)
     * 
     * 💡 示例：strip.SetBrightness(50); // 50%亮度
     */
    esp_err_t SetBrightness(uint8_t brightness);
    
    /**
     * 📈 淡入动画
     * @param color 目标颜色
     * @param duration_ms 持续时间（毫秒）
     * 
     * 💡 示例：strip.FadeIn(Color::RED, 2000); // 2秒淡入红色
     */
    esp_err_t FadeIn(const Color& color, uint32_t duration_ms);
    
    /**
     * 📉 淡出动画
     * @param duration_ms 持续时间（毫秒）
     * 
     * 💡 示例：strip.FadeOut(1000); // 1秒淡出
     */
    esp_err_t FadeOut(uint32_t duration_ms);
    
    /**
     * 🌈 彩虹动画
     * @param duration_ms 一个周期时间（毫秒）
     * 
     * 💡 示例：strip.Rainbow(3000); // 3秒一个彩虹周期
     */
    esp_err_t Rainbow(uint32_t duration_ms);
    
    /**
     * 💨 呼吸动画
     * @param color 呼吸颜色
     * @param period_ms 呼吸周期（毫秒）
     * @param cycles 循环次数（0=无限循环）
     * 
     * 💡 示例：strip.Breathe(Color::BLUE, 2000, 5); // 蓝色呼吸，2秒周期，5次
     */
    esp_err_t Breathe(const Color& color, uint32_t period_ms, uint32_t cycles = 0);
    
    /**
     * 🖌️ 颜色擦除动画（逐个点亮）
     * @param color 擦除颜色
     * @param delay_ms 每个LED延迟（毫秒）
     * 
     * 💡 示例：strip.ColorWipe(Color::GREEN, 100); // 绿色擦除，每个LED间隔100ms
     */
    esp_err_t ColorWipe(const Color& color, uint32_t delay_ms);
    
    /**
     * ✨ 闪烁动画（随机LED闪烁）
     * @param color 闪烁颜色
     * @param duration_ms 持续时间（毫秒）
     * @param density 闪烁密度 (1-100)
     * 
     * 💡 示例：strip.Sparkle(Color::WHITE, 5000, 20); // 白色闪烁5秒，密度20
     */
    esp_err_t Sparkle(const Color& color, uint32_t duration_ms, uint8_t density = 10);
    
    /**
     * 🏃 追逐动画（一段LED移动）
     * @param color 追逐颜色
     * @param chase_length 追逐长度
     * @param delay_ms 移动延迟（毫秒）
     * 
     * 💡 示例：strip.Chase(Color::RED, 5, 100); // 红色追逐，长度5，100ms移动一次
     */
    esp_err_t Chase(const Color& color, int chase_length, uint32_t delay_ms);
    
    /**
     * 🎭 剧院追逐动画（间隔点亮）
     * @param color 颜色
     * @param delay_ms 延迟时间（毫秒）
     * 
     * 💡 示例：strip.TheaterChase(Color::YELLOW, 200); // 黄色剧院追逐
     */
    esp_err_t TheaterChase(const Color& color, uint32_t delay_ms);
    
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                            颜色工具函数                                 ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /**
     * 🎨 HSV转RGB颜色
     * @param h 色调 (0.0-360.0)
     * @param s 饱和度 (0.0-1.0)
     * @param v 明度 (0.0-1.0)
     * @return RGB颜色
     * 
     * 💡 示例：Color red = HSVtoRGB(0, 1.0, 1.0); // 纯红色
     */
    static Color HSVtoRGB(float h, float s, float v);
    
    /**
     * 🔄 颜色插值（渐变）
     * @param from 起始颜色
     * @param to 结束颜色
     * @param factor 插值因子 (0.0-1.0)
     * @return 插值颜色
     * 
     * 💡 示例：Color mid = Interpolate(Color::RED, Color::BLUE, 0.5); // 红蓝中间色
     */
    static Color Interpolate(const Color& from, const Color& to, float factor);
    
    /**
     * 🎡 色轮函数（平滑颜色过渡）
     * @param pos 位置 (0-255)
     * @return 对应颜色
     * 
     * 💡 用途：创建彩虹效果
     */
    static Color Wheel(uint8_t pos);
    
    /**
     * 🎲 随机颜色生成
     * @return 随机RGB颜色
     * 
     * 💡 示例：Color random = RandomColor();
     */
    static Color RandomColor();
    
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              信息查询                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /// 📊 获取LED数量
    int GetLedCount() const { return led_count_; }
    
    /// ✅ 检查是否已初始化
    bool IsInitialized() const { return is_initialized_; }
    
    /// 🔆 获取当前亮度
    uint8_t GetBrightness() const { return brightness_; }
    
    /**
     * 🎨 获取指定LED的颜色
     * @param index LED索引
     * @return 颜色对象
     */
    Color GetPixelColor(int index) const;
    
    /// 🎬 获取当前动画类型
    AnimationType GetCurrentAnimation() const { return current_animation_; }
    
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              动画控制                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /// ⏹️ 停止当前动画
    void StopAnimation();
    
    /// ❓ 检查动画是否正在运行
    bool IsAnimationRunning() const { return animation_running_; }
    
    /// ⏸️ 暂停动画
    void PauseAnimation();
    
    /// ▶️ 恢复动画
    void ResumeAnimation();
    
    /// ❓ 检查动画是否暂停
    bool IsAnimationPaused() const { return animation_paused_; }

private:
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                              私有成员                                   ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    // 硬件配置
    int gpio_pin_;                          ///< GPIO引脚号
    int led_count_;                         ///< LED数量
    led_strip_handle_t led_strip_;         ///< ESP-IDF LED灯带句柄
    
    // 状态管理
    uint8_t brightness_;                    ///< 当前亮度 (0-100)
    bool is_initialized_;                   ///< 初始化状态
    
    // 动画控制
    AnimationType current_animation_;       ///< 当前动画类型
    bool animation_running_;                ///< 动画运行状态
    bool animation_paused_;                 ///< 动画暂停状态
    
    // 颜色状态
    std::vector<Color> current_colors_;     ///< 当前颜色状态
    
    // ╔════════════════════════════════════════════════════════════════════════╗
    // ║                            私有辅助函数                                 ║
    // ╚════════════════════════════════════════════════════════════════════════╝
    
    /// 🔆 应用亮度到颜色
    Color ApplyBrightness(const Color& color) const;
    
    /// 🔄 使用当前颜色刷新显示
    void RefreshWithCurrentColors();
    
    /// ✅ 验证LED索引有效性
    esp_err_t ValidateIndex(int index) const;
    
    /// 💡 内部设置像素函数
    esp_err_t SetPixelInternal(int index, const Color& color, bool refresh = true);
    
    /// ⏱️ 延迟函数
    void DelayMs(uint32_t ms) const;
};

#endif // WS2812_H 